package com.zqxx.examine.management.security.filter;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import org.apache.log4j.Logger;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.authentication.AuthenticationServiceException;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.AuthenticationException;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.security.web.authentication.UsernamePasswordAuthenticationFilter;
import org.springframework.util.StringUtils;

import com.zqxx.examine.management.security.StandardPasswordEncoderForSha1;
import com.zqxx.examine.management.security.UserInfo;

public class AuthenticationFilter
  extends UsernamePasswordAuthenticationFilter
{
  public static final String VALIDATE_CODE = "validate_code";
  public static final String USERNAME = "j_username";
  public static final String PASSWORD = "j_password";
  private static Logger log = Logger.getLogger(AuthenticationFilter.class);
  @Autowired
  public UserDetailsService userDetailsService;
  
  public Authentication attemptAuthentication(HttpServletRequest request, HttpServletResponse response)
    throws AuthenticationException
  {
    if (!request.getMethod().equals("POST")) {
      throw new AuthenticationServiceException("Authentication method not supported: " + request.getMethod());
    }
    String username = obtainUsername(request);
    String password = obtainPassword(request);
    

    String sh1Password = password + "{" + username + "}";
    PasswordEncoder passwordEncoder = new StandardPasswordEncoderForSha1();
    String result = passwordEncoder.encode(sh1Password);
    log.info(result);
    UserInfo userDetails = (UserInfo)this.userDetailsService.loadUserByUsername(username);
    if ((!passwordEncoder.matches(userDetails.getPassword(), result)) || ("0".equals(userDetails.getEnabled())) || (userDetails == null)) {
      throw new AuthenticationServiceException("用户名或密码错误！");
    }
    if ((!userDetails.getRolesName().contains("ROLE_ADMIN")) && (!userDetails.getRolesName().contains("ROLE_TEACHER"))) {
      throw new AuthenticationServiceException("非管理用户，操作无效！");
    }
    UsernamePasswordAuthenticationToken authRequest = new UsernamePasswordAuthenticationToken(username, password);
    setDetails(request, authRequest);
    Authentication authentication = null;
    try
    {
      authentication = getAuthenticationManager().authenticate(authRequest);
    }
    catch (Exception e)
    {
      log.error("auth error",e);
    }
    return authentication;
  }
  
  protected void checkValidateCode(HttpServletRequest request)
  {
    HttpSession session = request.getSession();
    
    String sessionValidateCode = obtainSessionValidateCode(session);
    

    String validateCodeParameter = obtainValidateCodeParameter(request);
    if ((StringUtils.isEmpty(validateCodeParameter)) || (!sessionValidateCode.equalsIgnoreCase(validateCodeParameter))) {
      throw new AuthenticationServiceException("验证码错误！");
    }
  }
  
  protected String obtainValidateCodeParameter(HttpServletRequest request)
  {
    Object obj = request.getParameter("validate_code");
    return null == obj ? "" : obj.toString().trim().toUpperCase();
  }
  
  protected String obtainSessionValidateCode(HttpSession session)
  {
    return null;
  }
  
  protected String obtainPassword(HttpServletRequest request)
  {
    Object obj = request.getParameter("j_password");
    return null == obj ? "" : obj.toString();
  }
  
  protected String obtainUsername(HttpServletRequest request)
  {
    Object obj = request.getParameter("j_username");
    return null == obj ? "" : obj.toString().trim().toLowerCase();
  }
}
